import React, { useEffect, useState } from 'react';
import { Box, FormDropdown, MainButton, makeToast, Text } from '@nova-hf/ui';
import { formatDate, makeDate } from 'beta/utils/helpers';
import { useTranslation } from 'beta/utils/i18n';
import { parseMainColor } from 'beta/utils/typeGuards';
import { addDays, addMonths, getDate, isSameDay } from 'date-fns';
import { useRouter } from 'next/router';
import { PaymentPlanDraft } from 'pages/thjonusta/stillingar/timabil/components/PaymentPlanDraft';
import { useCalculatePeriodQuery, useReactivateContractMutation } from 'typings/graphql';

interface EndurvirkjunProps {
  contractId: string;
  color?: string;
  onNext?(): void;
  currentDate?: Date | string;
}

const Endurvirkjun = ({ color, contractId, currentDate }: EndurvirkjunProps) => {
  const { t } = useTranslation(['stillingar']);
  const COLOR = parseMainColor(color ?? 'pink', 'pink');
  const router = useRouter();
  const customerId = router.query.customerId ?? '';
  const today = new Date();
  const [newDate, setNewDate] = useState(today);
  const [periods, setPeriods] = useState();
  const { data: calculatedData } = useCalculatePeriodQuery({
    variables: {
      input: {
        contractId: contractId.toString(),
        end: newDate,
        discount: 0,
        discountPercentage: 0,
      },
    },
  });

  const [reactivateContract] = useReactivateContractMutation({});
  const existingDate = makeDate(currentDate?.toString() ?? '');

  const makeOptions = (dueDate: Date) => {
    const availableDaysOfMonth = 28;
    const daysOptions: Array<React.ReactElement> = [];
    const today = new Date();

    const addOneDay = (date: Date) => {
      return addDays(date, 1);
    };

    let day = dueDate ? dueDate : today;

    for (let index = 0; index < availableDaysOfMonth; index = index + 1) {
      day = addOneDay(day);

      if (isSameDay(day, addMonths(dueDate ?? today, 1))) {
        break;
      }
      while (getDate(day) > availableDaysOfMonth) {
        day = addOneDay(day);
      }
      if (!isNaN(day.getTime())) {
        daysOptions.push(
          <option key={`option_${index + 1}`} value={day.toISOString().split('T')[0]}>
            {`${formatDate(day, 'd')}. ${t('period.perMonth')}`}
          </option>,
        );
      }
    }

    return daysOptions;
  };

  useEffect(() => {
    if (calculatedData) {
      setPeriods(calculatedData.calculateUpcomingCharges);
    }
  }, [calculatedData]);

  const onSubmit = async (chosenDate: Date) => {
    try {
      if (contractId) {
        const { data: reactivateContractData } = await reactivateContract({
          variables: {
            input: {
              id: contractId,
              end: chosenDate,
            },
          },
        });
        if (!reactivateContractData) {
          makeToast.danger(t('period.errors.newPeriod'), '');
        }
        if (reactivateContractData) {
          makeToast.success(t('period.errors.changeSuccess'), '');
          router.push(`/beta/${customerId}/askriftir/${contractId}`);
        }
      }
    } catch (error) {
      if (error instanceof Error) makeToast.danger(t('period.errors.newPeriod'), error.message);
    }
  };

  return (
    <Box>
      <Text variant="h5" marginBottom={5}>
        Breyta greiðsludegi
      </Text>
      <Text marginBottom={5}>{t('period.text', { date: formatDate(existingDate, 'd') })}</Text>
      <FormDropdown
        name="dayOfMonthSelect"
        label={newDate ? ' ' : t('period.dropdownLabel')}
        onSelect={(selection: Date) => {
          setNewDate(selection);
        }}
      >
        {makeOptions(existingDate)}
      </FormDropdown>
      {newDate && (
        <>
          <PaymentPlanDraft calculatedPeriods={periods} nextDueDate={existingDate} />
        </>
      )}
      <Box marginLeft="auto" marginTop={10} width="4/12">
        <MainButton
          dottedShadow="none"
          colorScheme={COLOR}
          text={t('period.confirm')}
          icon="longArrowRight"
          onClick={() => onSubmit(newDate)}
        />
      </Box>
    </Box>
  );
};

export default Endurvirkjun;
